#include "projectdefinitions.h"

void shuffle(void);
void pick_card(void);
void pick_card_up(void);
void hide_dealer_card(void);
void pick_dealer_card(void);
void print_number(void);
void dealer_play(void);
void LCD_results(void);
char my_uart(void);


///////////VARIABLES
	
	char card,number,symbol,player_sum=0,num_cards=0;
	char dealer_num, a_high=0, player_tot,a_high_d;
	int remaining=0,victory=0, loses=0;
	char state=0; //0 for befor playing, 1 for user playing, 2 for winning
				  //3 for losing, 4 for blackjack, 5 for Tie, 6 for dealer playing
	char deck[52];
	char decision=0;

PROGRAM_INIT
	ACTIVATE_LCD
	INIT_UART
	//defining symbols
	LCD_DEF(1, 0x04, 0x0A, 0x11, 0x11, 0x11, 0x0A, 0x0E, 0x1F) //Diamonds          
	LCD_DEF(2, 0x11, 0x0A, 0x15, 0x04, 0x04, 0x15, 0x0A, 0x11) //Hearts          
	LCD_DEF(3, 0x15, 0x0A, 0x15, 0x0A, 0x15, 0x0A, 0x15, 0x0A) //Spades          
	LCD_DEF(4, 0x00, 0x00, 0x1B, 0x15, 0x11, 0x0A, 0x04, 0x00) //Trebols  
	LCD_DEF(5,0x1F, 0x11, 0x15, 0x15, 0x15, 0x11, 0x1F, 0x00) //back card
	LCD_DEF(6,0x17, 0x15, 0x15, 0x15, 0x15, 0x15, 0x17, 0x00) //10
	//welcome screen
PROGRAM_START
	CLEAR_LCD
	LCD_TEXT(" Welcome to 21")
	LCD_XY(3,2)
	LCD_CHAR(0) // Display character #1
	LCD_TEXT("  ")
	LCD_CHAR(1) // Display character #2
	LCD_TEXT("  ")
	LCD_CHAR(2) // Display character #3
	LCD_TEXT("  ")
	LCD_CHAR(3) // Display character #4
	LCD_XY(2,3)
	LCD_TEXT(" For start B1 ")
	LCD_XY(2,4)
	LCD_TEXT(" For help B2")
	while((PINA & (1 << (0)))&&(PINA & (1 << (1))));//wait for b0 or b1
	{
		ON_BUTTON(2)
		{
			//help screen
			CLEAR_LCD
			LCD_TEXT(" Help!!!")
			LCD_XY(2,3)
			LCD_TEXT("<- Hit")
			LCD_XY(2,4)
			LCD_TEXT("Stand->")
			WAIT_FOR_RELEASE_BUTTON(2)
		}
		ON_BUTTON(1)
		{
			state=1;
			while(state==1)
			{
			if (remaining<10)
			{
				shuffle();
			}
		
			//Playing Screen
			CLEAR_LCD
			LCD_TEXT(" P ")
			pick_card_up();
			pick_card_up();
			LCD_XY(2,3)
			LCD_TEXT("D ")
			pick_dealer_card();					//update dealer sum
			hide_dealer_card();
			if(player_sum==21)  // BlackJack
			{
				state=4; //Blackjack
				WAIT_SEC(1)
				dealer_play();
			}
			else
			{
						//Gameplay
				while(state==1)
				{
					while((my_uart()<1)&((PINA & (1<<5))&&(PINA & (1<<7))));//wait for left or rigth joystick or uart
					
						if(decision==1)
						{
							pick_card_up();
							decision=0;
						}
						if(decision==2)
						{
							state=6;
							dealer_play();
							decision=0;
						}
						ON_JOYSTICK_LEFT
						{
							pick_card_up();
							WAIT_FOR_RELEASE_JOYSTICK_LEFT
						}
						ON_JOYSTICK_RIGHT
						{
							WAIT_FOR_RELEASE_JOYSTICK_RIGHT
							state=6; //dealer playing status
							dealer_play();
						}
					
				}
				
			}
			LCD_results();
			player_sum=0;
			num_cards=0;
			a_high_d=0;
			a_high=0;
			}
		}
	}


	
PROGRAM_END

void shuffle()
{
	//Shuffle Screen
	LCD_DEF(7, 0x00, 0x1F, 0x0E, 0x04, 0x0E, 0x1F, 0x00, 0x00)// vertical  
	LCD_DEF(8, 0x00, 0x11, 0x1B, 0x1F, 0x1F, 0x1B, 0x11, 0x00)// horizontal  
	LCD_CLEAR
	LCD_TEXT("   SHUFFLING")  
	LCD_XY(6,2)  
	LCD_TEXT(" ")  
	LCD_CHAR(6) // Display character #1  
	WAIT_SEC(0.3)  
	LCD_XY(6,2)  
	LCD_TEXT(" ")  
	LCD_CHAR(7) // Display character #1  
	WAIT_SEC(0.3)  
	LCD_XY(6,2)  
	LCD_TEXT(" ")  
	LCD_CHAR(6) // Display character #1
	WAIT_SEC(0.3)  
	LCD_XY(6,2) 
	LCD_TEXT(" ")  
	LCD_CHAR(7) 
	WAIT_SEC(1)
	remaining=260;
	for(int i=0;i<52;i++)
	{
		deck[i]=5;
	}
}

void pick_card()
{
	do
	{card=RANDOM(1,52);
	}while(deck[card-1]==0);	//if there are no more cards keep choosing a random number
	
		deck[card-1]=deck[card-1]-1;
		if(card<=13)
		{
			symbol=0;
		}
		if((card>13)&(card<=26))
		{
			symbol=1;
		}
		if((card>26)&(card<=39))
		{
			symbol=2;
		}
		if(card>39)
		{
			symbol=3;
		}
		number=card%13;
		print_number();
		LCD_CHAR(symbol)
		remaining=remaining-1;
		
	
}

void print_number()
{
	
		if((number>1)&(number<10))
			LCD_NUMBER(number)
		if(number==10)
			LCD_CHAR(5)
		if(number==0)
			{LCD_CHAR('K'); number=10;}
		if(number==11)
			{LCD_CHAR('J');number=10;}
		if(number==12)
			{LCD_CHAR('Q');number=10;}
		if(number==1)
			{LCD_CHAR('A'); number=11;
			if(state==1)a_high=a_high+1;
			if(state==6)a_high_d=a_high_d+1;
			}
}

void pick_card_up()
{
	num_cards=num_cards+1;
	if(num_cards<5)
		LCD_XY(1+(num_cards)*3,1)
	if(num_cards==5)
			LCD_XY(4,2)
	if(num_cards>9)
		LCD_XY(1+(num_cards-9)*3,3)
	if(num_cards>13)
		LCD_XY(1+(num_cards-13)*3,4)
	pick_card();
	player_sum=player_sum+number;
	if(state==1)
	{
		LCD_XY(15,2)
		if(player_sum>21) //chance to change an ace 11 for an ace 1
		{
			if(a_high>0)
			{
				player_sum=player_sum-10;
				a_high=a_high-1;
			}
		}
	}
	if((state==6)|(state==4))
	{
		LCD_XY(15,4)
		if(player_sum>21) //chance to change an ace 11 for an ace 1
		{
			if(a_high_d>0)
			{
				player_sum=player_sum-10;
				a_high_d=a_high_d-1;
			}
		}
	}
	LCD_NUMBER(player_sum)  
	WAIT_SEC(.5)
	if(num_cards==5)
	{
		if(player_sum<=21)
			state=2; //winning condition
	}
	if(player_sum>21) //check for greater than 21
	{
		if(state==1)
			state=3; //player busted lose condition
		if(state==6)
			state=2; //dealer busted winning condition
 	}
	
}

void pick_dealer_card()
{
	state=6;
	LCD_XY(4,3)
	pick_card();
	dealer_num=number;//store value
	state=1;
}

void hide_dealer_card()
{
	LCD_CHAR(' ')
	LCD_CHAR(4)
	LCD_CHAR(4)
	LCD_XY(15,4)
	LCD_NUMBER(dealer_num)
}

void dealer_play()
{
	player_tot=player_sum; //store total
	player_sum=dealer_num;
	a_high=0;
	num_cards=10;
	pick_card_up();
	WAIT_SEC(1)
	if(state==4)//blackjack victory=
	{
		if(player_sum==player_tot)//dealer=player (21=21?)
		{
			state=5;//tie
		}		
	}
	while(state==6) //dealer playing
	{
		if(player_sum>=player_tot)//dealer>=player
		{
			state=3;//player lose 
		}
		else
			pick_card_up(); //if not busted draw 1 more card
	}
}

void LCD_results()
{
	LCD_CLEAR
	if(state==2)
	{	
		LCD_TEXT(" PLAYER WIN ");
		victory=victory+1;
	}
		if(state==3)
	{	
		LCD_TEXT(" PLAYER LOSE ");
		loses=loses+1;
	}
		if(state==4)
	{	
		LCD_TEXT(" BLACKJACK ");
		victory=victory+1;
	}
		if(state==5)
	{	
		LCD_TEXT(" TIE ");
	}
	LCD_XY(2,3)
	LCD_TEXT("WINS   ")
	LCD_NUMBER(victory)
	LCD_XY(2,4)
	LCD_TEXT("LOSES  ")
	LCD_NUMBER(loses)
	WAIT_SEC(2)
	state=1; //keep playing
}


//UART
/*  'A' for master start comunication //master command
	'a' for slave start comunication after //slave command
	'B' for player_sum command //master command
	'b' for player_sum command confirmation //slave command
	'!'-'2' for player_sum //master command 33-50 ASCII; 4-21 sum
	'u' for player_sum confirm//slave command
	'C' for dealer_sum command// master command
	'c' for dealer_sum command confirm //slave command
	'3'-':' for dealer_sum// master command 51-60 ASCII; 2-11 sum		
	'v' for dealer_sum confirm; //slave command
	'D' hit decition command//master command
	'd' for hit//slave command
	'e' for stand// slave command
	'E' for end//master command

*/
char my_uart()
{
	char send,receive, out=0;
	char con=0; //0 ill, 1 online
	send='A';
	while(con<4)
	{
		UART_CHAR(send)
		UART_READ_CHAR(receive)
		if(receive=='a') 
		{
			if(con==0) con=1;
			send=('B');
		}
		if(con==1)
		{
			LCD_XY(2,1)
			LCD_CHAR('A')
			LCD_XY(2,2)
			LCD_CHAR('M')
			con=2;
			out=0;
		}
		if(receive=='b') 
		{
			send=(player_sum+29);  //player_sum + 29
		}
		if(receive=='u') 
		{
			send=('C');
		}
		if(receive=='c') 
		{
			send=(dealer_num+49); //dealer_sum + 49
		}
		if(receive=='v') 
		{
			send=('D');
		}
		if(receive=='d')
		{
			//LCD_TEXT("Hit")
			send=('E');
			decision=1;
			con=3;
		}
		if(receive=='e')
		{
			//LCD_TEXT("Stand")
			send=('E');
			con=3;
			decision=2;
		}

		//LCD_CHAR(receive)
		//LCD_CHAR(' ')
		if((con==0)|(con==3)) out=out+1;
		if(out>2)
		{
			con=4;
			LCD_XY(2,1)
			LCD_CHAR('P')
			LCD_XY(2,2)
			LCD_CHAR(' ')
			//LCD_TEXT("offline")
		}
		WAIT_SEC(.1)
	}
	return decision;
}
